//
//  THPlayerController.m
//  AVFoundationDemo
//
//  Created by rubick on 2019/1/17.
//  Copyright © 2019 LG. All rights reserved.
//

#import "THPlayerController.h"
#import <AVFoundation/AVFoundation.h>

@interface THPlayerController()<AVAudioPlayerDelegate>

@property (nonatomic) BOOL playing;
@property (strong, nonatomic) NSArray *players;

@end

@implementation THPlayerController

- (instancetype)init {
    self = [super init];
    if(self) {
        AVAudioPlayer *guitarPlayer = [self playerForFile:@"Canon"];
        AVAudioPlayer *bassPlayer = [self playerForFile:@"起风了"];
        AVAudioPlayer *drumsPlayer = [self playerForFile:@"三度和弦"];
        _players = @[guitarPlayer, bassPlayer, drumsPlayer];
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(handleInterruption:) name:AVAudioSessionInterruptionNotification object:[AVAudioSession sharedInstance]];
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(handleRouteChange:) name:AVAudioSessionRouteChangeNotification object:[AVAudioSession sharedInstance]];
    }
    return self;
}
- (AVAudioPlayer *)playerForFile:(NSString *)name {
    NSURL *fileURL = [[NSBundle mainBundle] URLForResource:name withExtension:@"mp3"];
    NSError *error = nil;
    AVAudioPlayer *player = [[AVAudioPlayer alloc] initWithContentsOfURL:fileURL error:&error];
    if(player) {
        player.numberOfLoops = -1;
        player.enableRate = YES;
        player.volume = 1;
        [player prepareToPlay];
        player.delegate = self;
    } else {
        NSLog(@"Error creating palyer: %@",[error localizedDescription]);
    }
    return player;
}
- (void)play {
    if(!self.playing) {
        NSTimeInterval delayTime = [self.players[0] deviceCurrentTime] + 0.01;
        for(AVAudioPlayer *player in self.players) {
            [player playAtTime:delayTime];
        }
        self.playing = YES;
    }
}
- (void)stop {
    if(self.playing) {
        for(AVAudioPlayer *player in self.players){
            [player stop];
            player.currentTime = 0.0f;
        }
        self.playing = NO;
    }
}
- (void)adjustRate:(float)rate {
    for(AVAudioPlayer *player in self.players) {
        player.rate = rate;
    }
}
- (void)adjustPan:(float)pan forPlayerAtIndex:(NSUInteger)index {
    if([self isValidIndex:index]) {
        AVAudioPlayer *player = self.players[index];
        player.pan = pan;
    }
}
- (void)adjustVolume:(float)volume forPlayerAtIndex:(NSUInteger)index {
    if([self isValidIndex:index]) {
        AVAudioPlayer *player = self.players[index];
        player.volume = volume;
    }
}
#pragma mark - private
- (BOOL)isValidIndex:(NSUInteger)index {
    return index == 0 || index < self.players.count;
}
// notification handle
- (void)handleInterruption:(NSNotification *)notification {
    NSDictionary *info = notification.userInfo;
    AVAudioSessionInterruptionType type = [info[AVAudioSessionInterruptionTypeKey] unsignedIntegerValue];
    if(type == AVAudioSessionInterruptionTypeBegan) {
        [self stop];
        if([self.delegate respondsToSelector:@selector(playbackStopped)]){
            [self.delegate playbackStopped];
        }
    } else {
        AVAudioSessionInterruptionOptions options = [info[AVAudioSessionInterruptionOptionKey] unsignedIntegerValue];
        if(options == AVAudioSessionInterruptionOptionShouldResume){
            [self play];
            if([self.delegate respondsToSelector:@selector(playbackBegan)]){
                [self.delegate playbackBegan];
            }
        }
    }
}
- (void)handleRouteChange:(NSNotification *)notification {
    NSDictionary *info = notification.userInfo;
    AVAudioSessionRouteChangeReason reason = [info[AVAudioSessionRouteChangeReasonKey] unsignedIntValue];
    if(reason == AVAudioSessionRouteChangeReasonOldDeviceUnavailable) {
        AVAudioSessionRouteDescription *previousRoute = info[AVAudioSessionRouteChangePreviousRouteKey];
        AVAudioSessionPortDescription *previousOutput = previousRoute.outputs[0];
        NSString *portType = previousOutput.portType;
        if([portType isEqualToString:AVAudioSessionPortHeadphones]) {
            [self stop];
            if([self.delegate respondsToSelector:@selector(playbackStopped)]) {
                [self.delegate playbackStopped];
            }
        }
    }
}
- (void)dealloc {
    [[NSNotificationCenter defaultCenter] removeObserver:self];
}
#pragma mark - Delegate
- (void)audioPlayerDidFinishPlaying:(AVAudioPlayer *)player successfully:(BOOL)flag {
    NSLog(@"%s",__func__);
}
- (void)audioPlayerDecodeErrorDidOccur:(AVAudioPlayer *)player error:(NSError * __nullable)error {
    NSLog(@"%s",__func__);
}

@end
